﻿using dz.loger.core;
using dz.u9.jky.schema.Common;
using dz.u9.jky.schema.InvDoc;
using dz.util.core;
using Dz.WorkerService.jkyschema;
using Dz.WorkerService.QueryParm;
using Dz.WorkerService.Utils;
using Microsoft.Data.SqlClient;
using System.Data;

namespace Dz.WorkerService
{
    /// <summary>
    /// 调入定时任务
    /// </summary>
    public class TaskTransferIn : BaseTaskItem
    {
        private string transInDocType, transInWh;
        

        public TaskTransferIn(string name, TimeSpan interval) : base(name, interval)
        {
            docType = "TransferIn";
            method = "oms.trade.fullinfoget";            
            table = "dz_jky_TransferIn";

            transInDocType = Config.Instance.GetValue("TransInDocType");
            transInWh = Config.Instance.GetValue("TransInWh");
        }


        protected override BaseParm BuildParm(DateTime sdate, DateTime edate)
        {
            TransferInParm parm = new TransferInParm();

            parm.startConsignTime = sdate.ToString("yyyy-MM-dd HH:mm:ss");
            parm.endConsignTime = edate.ToString("yyyy-MM-dd HH:mm:ss");
            parm.fields = @"tradeNo,chargeCurrency,goodsDetail.goodsNo,goodsDetail.sellCount,goodsDetail.unit,goodsDetail.platCode,goodsDetail.platGoodsId,
                            customerCode,warehouseCode,warehouseName,tradeId,shopcode,scrollId,goodsDetail.isFit,flagNames,goodsDetail.sellTotal,goodsDetail.taxFee,
                            tradeOrderAssemblyGoodsDtoList.sellTotal,tradeOrderAssemblyGoodsDtoList.taxFee,tradeOrderAssemblyGoodsDtoList.goodsNo,
                            tradeOrderAssemblyGoodsDtoList.taxRate,tradeOrderAssemblyGoodsDtoList.sellCount,tradeOrderAssemblyGoodsDtoList.sellTotal,flagNames";

            return parm;
        }

        private BaseParm RebuildParm(BaseParm parm, string scrollId)
        {
           TransferInParm rtn = parm as TransferInParm;

            rtn.scrollId = scrollId;

            return rtn;
        }
        protected override async Task DownLoadData(BaseParm parm)
        {
            await base.DownLoadData(parm);

            string scrollId = Guid.NewGuid().ToString();
            processId = scrollId;

            DataTable data = GetTable();            

            try
            {
                await InsertSyncLog(processId, docType);
                while (!string.IsNullOrEmpty(scrollId))
                {
                    WebResult result = await JkyUtils.Post(method, JsonUtil.Serialize(parm));

                    #region 判断http请求是否成功
                    if (!result.Sucess)
                        if (!result.Sucess)
                        {
                            throw new Exception($"下载{docType}失败：{result.Data}");
                        }
                    #endregion

                    #region 判断请求结构是否成功
                    JkyResult result1 = JsonUtil.Deserialize<JkyResult>(result.Data);
                    if (result1.code != 200)
                    {
                        throw new Exception($"下载{docType}失败：{result1.msg}");
                    }
                    #endregion

                    #region 处理请求结果
                    TradeResult result2 = JsonUtil.Deserialize<TradeResult>(result1.result.ToString());
                    scrollId = result2.data.scrollId;

                    parm = RebuildParm(parm, scrollId);
                    
                    if (result2.data.trades == null || result2.data.trades.Count == 0) continue;
                    foreach (TradeItem item in result2.data.trades)
                    {
                        AddData(data, item);
                    }
                    #endregion

                }
                await sqlUtils.Save(data, "dz_jky_TransferIn");
                await UpdateSyncLog(processId, 1);
                await UpdateDataState(1);
                await SetLastDate();
            }
            catch (Exception ex)
            {
                await UpdateSyncLog(processId, -1, ex.Message);
                LogUtil.Instance.Error($"同步{docType}失败：{ex.Message}");
                throw new Exception(ex.Message);
            }

        }

        /// <summary>
        /// 获得数据表
        /// </summary>
        /// <returns></returns>
        private DataTable GetTable()
        {
            DataTable table = new DataTable();

            
            table.Columns.Add("shopcode", typeof(string));
            table.Columns.Add("deptcode", typeof(string));
            table.Columns.Add("org", typeof(string));
            table.Columns.Add("wh", typeof(string)); 
            table.Columns.Add("tradeno", typeof(string));
            table.Columns.Add("tradeid", typeof(long));
            table.Columns.Add("goodsno", typeof(string));
            table.Columns.Add("sellcount", typeof(decimal));
            table.Columns.Add("platcode", typeof(string));
            table.Columns.Add("platcode", typeof(string));
            table.Columns.Add("flag", typeof(int));

            return table;
        }

        /// <summary>
        /// 新增数据
        /// </summary>
        /// <param name="dt"></param>
        /// <param name="item"></param>
        private void AddData(DataTable dt, TradeItem item)
        {
            if (item.flagNames.Contains("补录单")) return;

            int flag = item.flagNames.Contains("线下订单") ? 0 : 1;
            if (item.goodsDetail == null || item.goodsDetail.Count == 0) return;
            foreach (var row in item.goodsDetail)
            {
                //组合件需要从组装明细获取
                if (row.isFit == 1) continue;

                DataRow dr = dt.NewRow();
                
                dr["shopcode"] = item.shopCode;
                dr["deptcode"] = item.shopCode.Split("-")[0];
                dr["org"] = item.shopCode.Split("-")[1];
                dr["tradeno"] = item.tradeNo;
                dr["tradeid"] = item.tradeId;
                dr["goodsNo"] = row.goodsNo;
                dr["sellcount"] = row.sellCount;
                dr["platcode"] = row.platCode;
                dr["flag"] = flag;

                dt.Rows.Add(dr);
            }

            if (item.tradeOrderAssemblyGoodsDtoList == null || item.tradeOrderAssemblyGoodsDtoList.Count == 0) return;

            ///处理组装件
            foreach (var row in item.tradeOrderAssemblyGoodsDtoList)
            {
                DataRow dr = dt.NewRow();

                dr["shopcode"] = item.shopCode;
                dr["deptcode"] = item.shopCode.Split("-")[0];
                dr["org"] = item.shopCode.Split("-")[1];
                dr["tradeno"] = item.tradeNo;
                dr["tradeid"] = item.tradeId;
                dr["goodsNo"] = row.goodsNo;
                dr["sellcount"] = row.sellCount;

                dt.Rows.Add(dr);
            }

        }

        protected async override Task SyncToU9()
        {
            List<string> orgs = await GetOrgs();

            foreach (string org in orgs)
            {
                DzTransferIn transferIns = await GetTransferIn(org);

                U9CResult result = await U9Utils.Post(docType, "AddAndAudit", JsonUtil.Serialize(transferIns));

                await UpdateSyncLog(result,$" and org = {org}");
            }
        }

        private async Task<List<string>> GetOrgs()
        {
            string sql = "select distinct org from dz_jky_TransferIn where xtype = 1";

            SqlDataReader reader = await sqlUtils.GetDataReader(sql);

            List<string> rtn = new List<string>();

            while (reader.Read())
            {
                rtn.Add(reader["org"].ToString());
            }
            return rtn;

        }
        private async Task<DzTransferIn> GetTransferIn(string org)
        {
            string sql = @$"select sum(sellcount) as qty,goodsno as itemcode,wh from dz_jky_TransferIn where xtype = 1 and org = '{org}' and type = 1 
            group by goodsno,wh";

            DataTable dt = await sqlUtils.Fill(sql);

            #region 构建调入对象
            #region 表头
            DzTransferIn transferIn = new DzTransferIn();
            transferIn.TransInDocType = transInDocType;
            transferIn.Org = org;
            transferIn.BusinessDate = DateTime.Now;
            #endregion

            #region 明细
            List<DzTransInLine> lines = new List<DzTransInLine>();

            U9Utils u9Utils = new U9Utils();
            foreach (DataRow item in dt.Rows)
            {
                string inv = item["itemcode"].ToString();

                if (!InvUtils.Instance.IsExists(inv, org))
                {
                    LogUtil.Instance.Debug($"存货{inv}不存在，跳过");
                    continue;
                } 

                DzTransInLine line = new DzTransInLine();

                line.ItemInfo = item["itemcode"].ToString();
                line.CostUOMQty = Convert.ToDecimal(item["qty"]);
                line.StoreUOMQty = line.CostUOMQty;
                line.TransInWh = transInWh;

                #region 明细子行
                List<DzTransInSubLine> subLines = new List<DzTransInSubLine>();

                DzTransInSubLine subLine = new DzTransInSubLine();

                subLine.TransOutWh = item["wh"].ToString();
                subLine.TransOutOrg = org;

                subLines.Add(subLine);
                #endregion

                line.TransInSubLines = subLines;
                lines.Add(line);
            }


            #endregion

            #endregion
            

            return transferIn;

        }
    }
}
